<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Coroutine</title>
<link rel="stylesheet" href="../../../../../doc/src/boostbook.css" type="text/css">
<meta name="generator" content="DocBook XSL Stylesheets V1.79.1">
<link rel="home" href="../index.html" title="Chapter 1. Coroutine">
<link rel="up" href="../index.html" title="Chapter 1. Coroutine">
<link rel="prev" href="motivation.html" title="Motivation">
<link rel="next" href="coroutine/asymmetric.html" title="Asymmetric coroutine">
</head>
<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
<table cellpadding="2" width="100%"><tr>
<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../boost.png"></td>
<td align="center"><a href="../../../../../index.html">Home</a></td>
<td align="center"><a href="../../../../../libs/libraries.htm">Libraries</a></td>
<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
<td align="center"><a href="../../../../../more/index.htm">More</a></td>
</tr></table>
<hr>
<div class="spirit-nav">
<a accesskey="p" href="motivation.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="coroutine/asymmetric.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
</div>
<div class="section">
<div class="titlepage"><div><div><h2 class="title" style="clear: both">
<a name="coroutine.coroutine"></a><a class="link" href="coroutine.html" title="Coroutine">Coroutine</a>
</h2></div></div></div>
<div class="toc"><dl class="toc">
<dt><span class="section"><a href="coroutine/asymmetric.html">Asymmetric coroutine</a></span></dt>
<dd><dl>
<dt><span class="section"><a href="coroutine/asymmetric/pull_coro.html">Class <code class="computeroutput"><span class="identifier">asymmetric_coroutine</span><span class="special">&lt;&gt;::</span><span class="identifier">pull_type</span></code></a></span></dt>
<dt><span class="section"><a href="coroutine/asymmetric/push_coro.html">Class <code class="computeroutput"><span class="identifier">asymmetric_coroutine</span><span class="special">&lt;&gt;::</span><span class="identifier">push_type</span></code></a></span></dt>
</dl></dd>
<dt><span class="section"><a href="coroutine/symmetric.html">Symmetric coroutine</a></span></dt>
<dd><dl>
<dt><span class="section"><a href="coroutine/symmetric/symmetric_coro.html">Class
        <code class="computeroutput"><span class="identifier">symmetric_coroutine</span><span class="special">&lt;&gt;::</span><span class="identifier">call_type</span></code></a></span></dt>
<dt><span class="section"><a href="coroutine/symmetric/yield_coro.html">Class <code class="computeroutput"><span class="identifier">symmetric_coroutine</span><span class="special">&lt;&gt;::</span><span class="identifier">yield_type</span></code></a></span></dt>
</dl></dd>
</dl></div>
<p>
      <span class="bold"><strong>Boost.Coroutine</strong></span> provides two implementations
      - asymmetric and symmetric coroutines.
    </p>
<p>
      Symmetric coroutines occur usually in the context of concurrent programming
      in order to represent independent units of execution. Implementations that
      produce sequences of values typically use asymmetric coroutines. <a href="#ftn.coroutine.coroutine.f0" class="footnote" name="coroutine.coroutine.f0"><sup class="footnote">[5]</sup></a>
    </p>
<h4>
<a name="coroutine.coroutine.h0"></a>
      <span class="phrase"><a name="coroutine.coroutine.stackful"></a></span><a class="link" href="coroutine.html#coroutine.coroutine.stackful">stackful</a>
    </h4>
<p>
      Each instance of a coroutine has its own stack.
    </p>
<p>
      In contrast to stackless coroutines, stackful coroutines allow invoking the
      suspend operation out of arbitrary sub-stackframes, enabling escape-and-reenter
      recursive operations.
    </p>
<h4>
<a name="coroutine.coroutine.h1"></a>
      <span class="phrase"><a name="coroutine.coroutine.move_only"></a></span><a class="link" href="coroutine.html#coroutine.coroutine.move_only">move-only</a>
    </h4>
<p>
      A coroutine is moveable-only.
    </p>
<p>
      If it were copyable, then its stack with all the objects allocated on it would
      be copied too. That would force undefined behaviour if some of these objects
      were RAII-classes (manage a resource via RAII pattern). When the first of the
      coroutine copies terminates (unwinds its stack), the RAII class destructors
      will release their managed resources. When the second copy terminates, the
      same destructors will try to doubly-release the same resources, leading to
      undefined behaviour.
    </p>
<h4>
<a name="coroutine.coroutine.h2"></a>
      <span class="phrase"><a name="coroutine.coroutine.clean_up"></a></span><a class="link" href="coroutine.html#coroutine.coroutine.clean_up">clean-up</a>
    </h4>
<p>
      On coroutine destruction the associated stack will be unwound.
    </p>
<p>
      The constructor of coroutine allows you to pass a customized <span class="emphasis"><em>stack-allocator</em></span>.
      <span class="emphasis"><em>stack-allocator</em></span> is free to deallocate the stack or cache
      it for future usage (for coroutines created later).
    </p>
<h4>
<a name="coroutine.coroutine.h3"></a>
      <span class="phrase"><a name="coroutine.coroutine.segmented_stack"></a></span><a class="link" href="coroutine.html#coroutine.coroutine.segmented_stack">segmented
      stack</a>
    </h4>
<p>
      <span class="emphasis"><em>symmetric_coroutine&lt;&gt;::call_type</em></span>, <span class="emphasis"><em>asymmetric_coroutine&lt;&gt;::push_type</em></span>
      and <span class="emphasis"><em>asymmetric_coroutine&lt;&gt;::pull_type</em></span> support segmented
      stacks (growing on demand).
    </p>
<p>
      It is not always possible to accurately estimate the required stack size -
      in most cases too much memory is allocated (waste of virtual address-space).
    </p>
<p>
      At construction a coroutine starts with a default (minimal) stack size. This
      minimal stack size is the maximum of page size and the canonical size for signal
      stack (macro SIGSTKSZ on POSIX).
    </p>
<p>
      At this time of writing only GCC (4.7) <a href="#ftn.coroutine.coroutine.f1" class="footnote" name="coroutine.coroutine.f1"><sup class="footnote">[6]</sup></a> is known to support segmented stacks. With version 1.54 <span class="bold"><strong>Boost.Coroutine</strong></span> provides support for segmented stacks.
    </p>
<p>
      The destructor releases the associated stack. The implementer is free to deallocate
      the stack or to cache it for later usage.
    </p>
<h4>
<a name="coroutine.coroutine.h4"></a>
      <span class="phrase"><a name="coroutine.coroutine.context_switch"></a></span><a class="link" href="coroutine.html#coroutine.coroutine.context_switch">context
      switch</a>
    </h4>
<p>
      A coroutine saves and restores registers according to the underlying ABI on
      each context switch (using <span class="bold"><strong>Boost.Context</strong></span>).
    </p>
<p>
      Some applications do not use floating-point registers and can disable preserving
      FPU registers for performance reasons.
    </p>
<div class="note"><table border="0" summary="Note">
<tr>
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../doc/src/images/note.png"></td>
<th align="left">Note</th>
</tr>
<tr><td align="left" valign="top"><p>
        According to the calling convention the FPU registers are preserved by default.
      </p></td></tr>
</table></div>
<p>
      On POSIX systems, the coroutine context switch does not preserve signal masks
      for performance reasons.
    </p>
<p>
      A context switch is done via <span class="emphasis"><em>symmetric_coroutine&lt;&gt;::call_type::operator()</em></span>,
      <span class="emphasis"><em>asymmetric_coroutine&lt;&gt;::push_type::operator()</em></span> and
      <span class="emphasis"><em>asymmetric_coroutine&lt;&gt;::pull_type::operator()</em></span>.
    </p>
<div class="warning"><table border="0" summary="Warning">
<tr>
<td rowspan="2" align="center" valign="top" width="25"><img alt="[Warning]" src="../../../../../doc/src/images/warning.png"></td>
<th align="left">Warning</th>
</tr>
<tr><td align="left" valign="top"><p>
        Calling <span class="emphasis"><em>symmetric_coroutine&lt;&gt;::call_type::operator()</em></span>,
        <span class="emphasis"><em>asymmetric_coroutine&lt;&gt;::push_type::operator()</em></span>
        and <span class="emphasis"><em>asymmetric_coroutine&lt;&gt;::pull_type::operator()</em></span>
        from inside the <span class="underline">same</span> coroutine results
        in undefined behaviour.
      </p></td></tr>
</table></div>
<p>
      As an example, the code below will result in undefined behaviour:
    </p>
<pre class="programlisting"><span class="identifier">boost</span><span class="special">::</span><span class="identifier">coroutines</span><span class="special">::</span><span class="identifier">symmetric_coroutine</span><span class="special">&lt;</span><span class="keyword">void</span><span class="special">&gt;::</span><span class="identifier">call_type</span> <span class="identifier">coro</span><span class="special">(</span>
    <span class="special">[&amp;](</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">coroutines</span><span class="special">::</span><span class="identifier">symmetric_coroutine</span><span class="special">&lt;</span><span class="keyword">void</span><span class="special">&gt;::</span><span class="identifier">yield_type</span><span class="special">&amp;</span> <span class="identifier">yield</span><span class="special">){</span>
        <span class="identifier">yield</span><span class="special">(</span><span class="identifier">coro</span><span class="special">);</span> <span class="comment">// yield to same symmetric_coroutine</span>
<span class="special">});</span>
<span class="identifier">coro</span><span class="special">();</span>
</pre>
<div class="footnotes">
<br><hr style="width:100; text-align:left;margin-left: 0">
<div id="ftn.coroutine.coroutine.f0" class="footnote"><p><a href="#coroutine.coroutine.f0" class="para"><sup class="para">[5] </sup></a>
        Moura, Ana Lucia De and Ierusalimschy, Roberto. "Revisiting coroutines".
        ACM Trans. Program. Lang. Syst., Volume 31 Issue 2, February 2009, Article
        No. 6
      </p></div>
<div id="ftn.coroutine.coroutine.f1" class="footnote"><p><a href="#coroutine.coroutine.f1" class="para"><sup class="para">[6] </sup></a>
        <a href="http://gcc.gnu.org/wiki/SplitStacks" target="_top">Ian Lance Taylor, Split
        Stacks in GCC</a>
      </p></div>
</div>
</div>
<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
<td align="left"></td>
<td align="right"><div class="copyright-footer">Copyright © 2009 Oliver Kowalke<p>
        Distributed under the Boost Software License, Version 1.0. (See accompanying
        file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
      </p>
</div></td>
</tr></table>
<hr>
<div class="spirit-nav">
<a accesskey="p" href="motivation.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="coroutine/asymmetric.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
</div>
</body>
</html>
